/* Copyright (c) 2004-2024 Peigen.info. All rights reserved. */
package info.peigen.hotpot.common.service.base;

import cn.hutool.core.util.ObjectUtil;
import info.peigen.hotpot.common.core.result.ResultBase;
import jakarta.validation.ConstraintViolationException;

/**
 * <b>(ServiceInvoke)</b>
 * 服务层接口,待具体的服务去实现
 *
 * @author Peigen
 * @version 1.0.0
 * @since 2019/05/19
 */
@SuppressWarnings({"rawtypes", "unchecked", "CallToPrintStackTrace"})
public interface ServiceInvoke {

    /**
     * 大多数的入参都可以在api层拦截，但是需要根据条件组合的入参校验目前不支持<br/>
     * 先用这样的方法顶一顶
     *
     * @param serviceContext 服务上下文
     */
    default void checkOrder(ServiceContext serviceContext) {
        if (ObjectUtil.isNotNull(serviceContext.getOrder())) {
            serviceContext.getOrder().check();
        }
    }

    /**
     * 初始化交易日志
     *
     * @param serviceContext 服务上下文
     */
    default void initialDataLog(ServiceContext serviceContext) {
    }

    /**
     * 初始化请求
     *
     * @param serviceContext 服务上下文
     */
    default void installRequest(ServiceContext serviceContext) {
    }

    /**
     * 构建Mock
     *
     * @param serviceContext 服务上下文
     */
    default void mock(ServiceContext serviceContext) {
    }

    /**
     * 数据持久化，当数据需要两阶段持久化时，则在匿名内部类中实现此方法
     *
     * @param serviceContext 服务上下文
     */
    default void handleInitDataEvent(ServiceContext serviceContext) {
    }

    /**
     * 业务执行代码
     *
     * @param serviceContext 服务上下文
     */
    void invoke(ServiceContext serviceContext);

    /**
     * 发送异步[数据存储]事件
     *
     * @param serviceContext 服务上下文
     */
    default void handleStoreDataEvent(ServiceContext serviceContext) {
        serviceContext.getResult().failure();
    }

    /**
     * 根据不同的情况下，对于异常的处理<br/>
     *
     * @param e              异常
     * @param serviceContext 服务上下文
     */
    default void handleException(Exception e, ServiceContext serviceContext) {
        // 初始化一个空的Result
        if (ObjectUtil.isNull(serviceContext.getResult())) {
            serviceContext.setResult(new ResultBase());
        }

        // 参数异常封装
        if (e instanceof ConstraintViolationException || e instanceof IllegalArgumentException) {
            serviceContext.getResult().setFailForParaError(e.getMessage());
            return;
        }

        // 异常处理不规范的时候，打印堆栈，后续优化
        e.printStackTrace();

        // 底层系统异常（未捕获的数据库异常等）
        serviceContext.getResult().setInternalError("系统内部错误");
    }
}